package course.ya.doc.from.code.model.lexer.project;

import java.util.LinkedHashMap;
import java.util.Map;
import java.util.StringTokenizer;

public class WrapperScanner {

    private String fileName;
    private String sourceCode;
    private String delimiters;
    private String[] delimetersArray;

    public WrapperScanner(String sourceCode) {
        this.sourceCode = sourceCode;
        Delimiters del = new Delimiters();
        this.delimiters = del.toString();
        this.delimetersArray = del.getDelimiters();
        this.fileName = "";
    }

    public Map<Keys, SyntaxTree> scan() {
        String token = "";
        String nextToken = "";
        StringTokenizer st
                = new StringTokenizer(this.sourceCode, this.delimiters, true);
        Map<Keys, SyntaxTree> treeMap = new LinkedHashMap<Keys, SyntaxTree>();
        SyntaxTree tree = new SyntaxTree();
        String className = "";

        String packageName = "";
        boolean isPackage = false;

        while (st.hasMoreTokens()) {
            token = st.nextToken();
            if (st.hasMoreTokens()) {
                nextToken = st.nextToken();
            }

            if (!nextToken.equals(delimetersArray[1])) {
                token = token.trim();
                if (nextToken.equals(delimetersArray[0])) {
                    String[] split = token.split(" ");
                    if (!split[0].equals("import")) {
                        tree.insert(token, false, false);
                    }
                    if (isPackage == false) {
                        if (split[0].equals("package")) {
                            packageName = split[1];
                            isPackage = true;
                        }
                    }
                }

            } else {
                int count = 0;
                token = token.trim();
                String[] splitter = token.split(" ");
                if (splitter[splitter.length - 2].equals("implements")) {
                    className = splitter[splitter.length - 3];
                } else {
                    className = splitter[splitter.length - 1];
                }

                String methodName = "";

                token = token.trim();
                tree.insert(token, false, true);

                while (st.hasMoreTokens()) {
                    token = st.nextToken();
                    if (st.hasMoreTokens()) {
                        nextToken = st.nextToken();
                    } else {
                        nextToken = delimetersArray[0];
                    }
                    if (nextToken.equals(delimetersArray[0])) {
                        token = token.trim();
                        if (!token.equals("")) {
                            tree.insert(token, false, false);
                        }
                    } else {
                        StringBuilder sb = new StringBuilder();

                        if (nextToken.equals(delimetersArray[1])) {
                            count++;
                            token = token.trim();

                            methodName = token;
                            tree.insert(token, false, false);
                            sb.append(methodName).append(delimetersArray[1]);

                            while (st.hasMoreTokens()) {
                                token = st.nextToken();
                                nextToken = st.nextToken();

                                if (nextToken.equals(delimetersArray[2])) {
                                    count--;
                                } else {
                                    if (nextToken.equals(delimetersArray[1])) {
                                        count++;
                                    }
                                }
                                sb.append(token).append(nextToken);
                                if (count == 0) {
                                    break;
                                }
                            }

                            Delimiters del = new Delimiters();
                            Scanner scanner = new Scanner(sb.toString(), del.getDelimiters());
                            scanner.scan();

                            Keys key = new Keys(methodName, packageName + "." + className + " " + methodName);
                            treeMap.put(key, scanner.returnTree());

                            sb = null;
                        } else {
                            if (nextToken.equals(delimetersArray[2])) {
                                Keys keyMap = new Keys(className, packageName + "." + className);
                                treeMap.put(keyMap, tree);
                                if (st.hasMoreTokens()) {
                                    token = st.nextToken();
                                }
                            }
                        }
                    }
                }
            }
        }
        Keys keyMap = new Keys(className, packageName + "." + className);
        treeMap.put(keyMap, tree);
        return treeMap;
    }
}
